package com.xu.tools.util;

import com.xu.tools.mapstruct.UserDTO;
import com.xu.tools.mapstruct.UserVO;
import org.springframework.beans.BeanUtils;
import org.springframework.lang.Nullable;
import org.springframework.util.StringUtils;

import java.beans.PropertyDescriptor;
import java.lang.reflect.Method;

/**
 * 自动生成实体类之间转换的setXXX方法
 *
 * @author xuguan
 * @since 2024/3/27
 */
public class ConverterPrintUtil {
    public static void print(Class<?> sourceCls, Class<?> targetCls, @Nullable String sourceName, @Nullable String targetName) {
        if (!StringUtils.hasText(sourceName)) {
            sourceName = StringUtils.uncapitalize(sourceCls.getSimpleName());
        }
        if (!StringUtils.hasText(targetName)) {
            targetName = StringUtils.uncapitalize(targetCls.getSimpleName());
        }

        final PropertyDescriptor[] sourcePds = BeanUtils.getPropertyDescriptors(sourceCls);
        final PropertyDescriptor[] targetPds = BeanUtils.getPropertyDescriptors(targetCls);

        String initializeWords = "final " + targetCls.getSimpleName() + " " + targetName + " = new " + targetCls.getSimpleName() + "();";
        System.out.println(initializeWords);
        for (PropertyDescriptor targetPd : targetPds) {
            final Method targetPdWriteMethod = targetPd.getWriteMethod();

            // 跳过getClass()方法
            if (targetPd.getName().equals("class")) {
                continue;
            }

            // 默认set方法赋值null
            String setWords = targetName + "." + targetPdWriteMethod.getName() + "(null);";

            // 遍历source中的属性, 如果属性名一致, set方法赋值为对应的get方法
            for (PropertyDescriptor sourcePd : sourcePds) {
                if (targetPd.getName().equals(sourcePd.getName())) {
                    final Method sourcePdReadMethod = sourcePd.getReadMethod();
                    setWords = targetName + "." + targetPdWriteMethod.getName() + "(" + sourceName + "." + sourcePdReadMethod.getName() + "());";
                    break;
                }
            }
            System.out.println(setWords);
        }
    }

    public static void main(String[] args) {
        // Demo
        print(UserDTO.class, UserVO.class, null, null);
    }
}

